﻿using System;
using System.Linq;
using System.Web.Mvc;
using System.ComponentModel;
using System.Web.Security;
using CVsharp.MVClib.Authorize;

namespace CVsharp.MVClib.Authorize
{
    [AttributeUsage(AttributeTargets.Class | AttributeTargets.Method, AllowMultiple = false)]
    public class AuthorizeFilterAttribute : ActionFilterAttribute
    {
        public override void OnActionExecuting(ActionExecutingContext filterContext)
        {
            if (filterContext == null)
            {
                throw new ArgumentNullException("filterContext");
            }
            var path = filterContext.HttpContext.Request.Path.ToLower();
            if (path == "/Account/LogOn".ToLower() || path == "/Account/Register".ToLower())
            {
                return; //忽略对Login登录页的权限判定
            }
            if (Membership.GetUser() != null)
            {
                if (Membership.GetUser().UserName == "admin")
                {
                    return; //忽略对超级管理员的权限判断用于开发测试
                }
            }
            if (Roles.IsUserInRole("admin"))
            {
                return; //忽略对超级管理员的权限判断
            }
            #region 当前Action所以人都可以访问
            object[] isAllPermissionAttrs = filterContext.ActionDescriptor.GetCustomAttributes(typeof(IsAllPermissionAttribute), true);
            var isAllPermission = isAllPermissionAttrs.Length == 1;//表示当前Action所以人都可以访问
            if (isAllPermission)
            {
                return; 
            }
            #endregion
            #region 判定用户是否登录，不是，跳转到登录页面
            if (!filterContext.HttpContext.User.Identity.IsAuthenticated)
            {
                filterContext.Result = new RedirectResult("/Account/Out");
                return;
            }

            #endregion  
            #region 获取该页名称
            object[] Descriptions = filterContext.ActionDescriptor.GetCustomAttributes(typeof(DescriptionAttribute), true);
            string Description = string.Empty;
            if (Descriptions.Length > 0)
                Description = (Descriptions[0] as DescriptionAttribute).Description;
            #endregion     
          
            #region 当前Action请求是否为具体的页面
            object[] isViewPageAttrs = filterContext.ActionDescriptor.GetCustomAttributes(typeof(IsViewPageAttribute), true);
            var isViewPage = isViewPageAttrs.Length == 1;//当前Action请求是否为具体的功能页
            #endregion           
            //注：如果未登录直接在URL输入功能权限地址提示不是很友好；如果登录后输入未维护的功能权限地址，那么也可以访问，这个可能会有安全问题
            if (AuthorizeCore(filterContext, isViewPage))
            {
                return;
            }
            if (isViewPage)
            {
                //filterContext.Result = new ContentResult { Content = @"外部登录：请登录系统！" };//功能权限弹出提示框
                //filterContext.Result = new HttpUnauthorizedResult();//直接URL输入的页面地址跳转到登陆页
                filterContext.HttpContext.Response.StatusCode = 404;
                filterContext.Result = new ContentResult { Content = @"您没有权限访问" + Description + "的页面！" };//功能权限弹出提示框
            }
            else
            {
                //ContentResult cr = new ContentResult();
                //cr.Content = @"alertMsg.error('您没有权限执行这个操作！');";
                //cr.ContentType = "application/x-javascript";
                //JavaScriptResult cr = new JavaScriptResult();
                //cr.Script = @"alertMsg.error('您没有权限执行这个操作！');";
                //filterContext.Result = cr;
                filterContext.HttpContext.Response.StatusCode = 404;
                filterContext.Result = new ContentResult { Content = @"您没有权限执行" + Description + "此功能！" };
            }
        }
        /// <summary>
        /// 权限判断业务逻辑,需要在这里添加
        /// </summary>
        /// <param name="filterContext"></param>
        /// <param name="isViewPage"></param>
        /// <returns></returns>
        protected virtual bool AuthorizeCore(ActionExecutingContext filterContext, bool isViewPage)
        {
            if (filterContext.HttpContext == null)
            {
                throw new ArgumentNullException("filterContext");
            }
            var user = new CurrentUserAccount(); //获取当前用户信权限息
            var controllerName = filterContext.RouteData.Values["controller"].ToString();
            var actionName = filterContext.RouteData.Values["action"].ToString();
            if (controllerName.ToLower() == "home" && actionName.ToLower() == "index") //过滤主页
            {
                return true;
            }
            if (controllerName.ToLower() == "account" && actionName.ToLower() == "logoff")
            {
                return true;
            }
            if (user.ActionPermission.Count(a => a.ControllerName == controllerName && a.ActionName == actionName) == 0)
            {
                return false;
            }
            return true;
        }
    }
}
